﻿using MvvmFoundation.Wpf;
using ServiceOperater.Helpers;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.IO;
using System.Linq;
using System.Text;
using System.Windows;

namespace ServiceOperater.ViewModels
{
    /*
        TreeView中的每一个TreeViewItem的数据源
     *   代表一个文件夹/文件
     */
    public sealed class FileTreeNodeViewModel : ObservableObject
    {

        public FileTreeNodeViewModel(string text, string fullPath, FileTreeNodeViewModel parent)
        {
            this.Text = text;
            this.FullPath = fullPath;
            this.Parent = parent;
            this.IsDirectory = FileHelper.isDir(fullPath);
            this.Children = new ObservableCollection<FileTreeNodeViewModel>();
            this.ServiceCollection = new ObservableCollection<ServiceTreeNodeViewModel>();

            instantiateCommand();
        }

        private void instantiateCommand()
        {
            CopyFilePathCommand = new RelayCommand<FileTreeNodeViewModel>((selectedFtnvm) =>
            {
                var fileFullPath = selectedFtnvm.FullPath;
                // http://www.cnblogs.com/zhaotianff/p/5841942.html
                // 第二个参数设置为false，或者不设置，将在程序运行结束后不保留剪切板内容。
                Clipboard.SetDataObject(fileFullPath, true);
            }, (selectedFtnvm) =>
            {
                return true;
            });

            OnSearchServiceTxtChangedCommand = new RelayCommand<String>((searchTxt) =>
            {
                if (String.IsNullOrWhiteSpace(searchTxt))
                {
                    foreach (var serviceVm in ServiceCollection)
                    {
                        serviceVm.IsHighight = false;
                    }
                    return;
                }

                foreach (var serviceVm in ServiceCollection)
                {
                    if (String.IsNullOrWhiteSpace(searchTxt))
                    {
                        serviceVm.IsHighight = false;
                        return;
                    }
                    serviceVm.IsHighight = (serviceVm.Id.ToLowerInvariant().Contains(searchTxt.ToLowerInvariant()));
                }
            }, (selectedFtnvm) =>
            {
                return ServiceCollection.Count > 0;
            });

            OnServiceTreeNodeSelectionChangedCommand = new RelayCommand<Object>((selectedTreeNode) =>
            {
                ServiceTreeNodeViewModel currentStnVm = null;
                if (selectedTreeNode is ServiceTreeNodeViewModel)
                {
                    var sTnvm = (selectedTreeNode as ServiceTreeNodeViewModel);
                    // 所有的都闭合
                    foreach (var item in sTnvm.ActionChildren)
                    {
                        item.IsSelected = false;
                    }

                    currentStnVm = sTnvm;
                }
                else if (selectedTreeNode is ActionTreeNodeViewModel)
                {
                    // 只打开选中的那个
                    var aTnvm = selectedTreeNode as ActionTreeNodeViewModel;
                    foreach (var aItem in aTnvm.Parent.ActionChildren)
                    {
                        if (aItem == aTnvm)
                        {
                            continue;
                        }
                        aItem.IsSelected = false;
                    }

                    currentStnVm = aTnvm.Parent;
                }

                if (currentStnVm == null)
                {
                    return;
                }
                //筛选JS文件中包含该service的
                List<FoundFileInfo> locationList = FileFinder.Find(ConfigHelper.FrontFolderPath, "*.js", currentStnVm.Id);
                currentStnVm.FoundFileInfoList.Clear();
                foreach (var item in locationList)
                {
                    currentStnVm.FoundFileInfoList.Add(item);
                }
            }, (selectedTreeNode) =>
            {
                return true;
            });

            CopyServiceNameCommand = new RelayCommand<ServiceTreeNodeViewModel>((selectedStnVm) =>
            {
                //var fileFullPath = Path.GetFileName(selectedStnVm.Id);
                // 第二个参数设置为false，或者不设置，将在程序运行结束后不保留剪切板内容。
                Clipboard.SetDataObject(selectedStnVm.Id, true);
            });

            // 失去焦点时,或外界主动调用
            SaveFileNameCommand = new RelayCommand<FileTreeNodeViewModel>((selectedFtnvm) =>
            {
                String finallyFileFullName = Path.Combine(Directory.GetParent(selectedFtnvm.FullPath).FullName, selectedFtnvm.Text);
                if (finallyFileFullName != selectedFtnvm.FullPath)
                {
                    //File.Move();
                    // 下面这个既可以移动目录, 也可以移动文件; 上面的只能移动文件
                    Directory.Move(selectedFtnvm.FullPath, finallyFileFullName);
                }
                selectedFtnvm.IsInEditMode = false;

                App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_APPLY, selectedFtnvm);
            }, (selectedFtnvm) =>
            {
                return true;
            });

            //F2,右键菜单
            ModifyServiceNameCommand = new RelayCommand<Object>((selectedSa) =>
            {
                if (selectedSa is ServiceTreeNodeViewModel)
                {
                    ((ServiceTreeNodeViewModel)selectedSa).IsInEditMode = true;
                }
                else if (selectedSa is ActionTreeNodeViewModel)
                {
                    ((ActionTreeNodeViewModel)selectedSa).IsInEditMode = true;
                }

            }, (selectedSa) =>
            {
                return true;
            });

            // Enter; 保存service或action的名称; 失去焦点时候也会调用; 因为会认为你提交了
            SaveServiceOrActionNameCommand = new RelayCommand<Object>((selectedSa) =>
            {

                // 先检索到原始值
                App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_RETRIEVAL, selectedSa);
                // 
                if (selectedSa is ServiceTreeNodeViewModel)
                {
                    var serviceRecord = ((ServiceTreeNodeViewModel)selectedSa);
                    serviceRecord.IsInEditMode = false;
                    if (!serviceRecord.IsVirtual)
                    {
                        ServiceFileOperater.ModifyServiceName(serviceRecord);
                    }
                }
                else if (selectedSa is ActionTreeNodeViewModel)
                {
                    var currentActionRecord = ((ActionTreeNodeViewModel)selectedSa);
                    currentActionRecord.IsInEditMode = false;
                    if (!currentActionRecord.IsVirtual)
                    {
                        // 上面检索了action的值, 我们还要检索service的值
                        App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_RETRIEVAL, currentActionRecord.Parent);
                        ServiceFileOperater.ModifyActionName(currentActionRecord);
                    }

                }

                App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_APPLY, selectedSa);
            }, (selectedSa) =>
            {
                return true;
            });

            //Cancel
            CancelEditServiceNameCommand = new RelayCommand<Object>((selectedSa) =>
            {
                if (selectedSa is ServiceTreeNodeViewModel)
                {
                    ((ServiceTreeNodeViewModel)selectedSa).IsInEditMode = false;
                }
                else if (selectedSa is ActionTreeNodeViewModel)
                {
                    ((ActionTreeNodeViewModel)selectedSa).IsInEditMode = false;
                }
                App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_ROLLBACK, selectedSa);
            }, (selectedSa) =>
            {
                return true;
            });

            DelServiceOrActionNameCommand = new RelayCommand<Object>((selectedSa) =>
            {
                // 先检索到原始值,可能是service,也可能是action
                App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_RETRIEVAL, selectedSa);

                if (selectedSa is ServiceTreeNodeViewModel)
                {
                    var serviceRecord = ((ServiceTreeNodeViewModel)selectedSa);
                    if (serviceRecord.IsVirtual)
                    {
                        ServiceCollection.Remove(serviceRecord);
                        return;
                    }

                    var isRemovedSuccess = ServiceFileOperater.RemoveServiceNode(serviceRecord);
                    if (isRemovedSuccess)
                    {
                        ServiceCollection.Remove(serviceRecord);
                    }
                }
                else if (selectedSa is ActionTreeNodeViewModel)
                {
                    var actionRecord = ((ActionTreeNodeViewModel)selectedSa);
                    if (actionRecord.IsVirtual)
                    {
                        actionRecord.Parent.ActionChildren.Remove(actionRecord);
                        return;
                    }
                    // 先检索到原始值,上面检索的是action
                    App.Messenger.NotifyColleagues(MessengerToken.TRANSACTION_RETRIEVAL, actionRecord.Parent);
                    var isRemovedSuccess = ServiceFileOperater.RemoveActionNode(actionRecord);
                    if (isRemovedSuccess)
                    {
                        actionRecord.Parent.ActionChildren.Remove(actionRecord);
                    }
                }

            }, (selectedSa) =>
            {
                return true;
            });

            // 新建Service, 单独的service不会被保存, 只有在保存action时才会真正去保存service
            AddServiceCommand = new RelayCommand<FileTreeNodeViewModel>((selectedFtnvm) =>
            {
                var willAddedService = new ServiceTreeNodeViewModel("~~~~", selectedFtnvm)
                {
                    IsInEditMode = true,
                    IsSelected = true,
                    IsVirtual = true
                };

                willAddedService.AddActionCommand.Execute(willAddedService);

                this.ServiceCollection.Add(willAddedService);
            }, (selectedFtnvm) =>
            {
                return true;
            });

            OpenLocationFileCommand = new RelayCommand<Object>((selectedSa) =>
            {
                if (selectedSa is ServiceTreeNodeViewModel)
                {
                    var serviceRecord = ((ServiceTreeNodeViewModel)selectedSa);
                    if (serviceRecord.IsVirtual)
                    {
                        return;
                    }

                    System.Diagnostics.Process.Start(ConfigHelper.TextEditorPath, serviceRecord.LocationFile.FullPath);
                }
                else if (selectedSa is ActionTreeNodeViewModel)
                {
                    var actionRecord = ((ActionTreeNodeViewModel)selectedSa);
                    if (actionRecord.IsVirtual)
                    {
                        return;
                    }

                    System.Diagnostics.Process.Start(ConfigHelper.TextEditorPath, actionRecord.Parent.LocationFile.FullPath);
                }

            }, (selectedSa) =>
            {
                return true;
            });
        }

        #region Props
        // 
        private string text = string.Empty;
        public string Text
        {
            get
            {
                return text;
            }
            set
            {
                if (text == value)
                {
                    return;
                }

                text = value;

                // TODO 保存起来！

                RaisePropertyChanged("Text");
            }
        }

        // ----
        // 是否目录
        public bool IsDirectory { get; private set; }

        // 文件中的内容是否被修改
        private bool isModified = false;
        public bool IsModified
        {
            get
            {
                return isModified;
            }
            set
            {
                if (isModified == value)
                {
                    return;
                }

                isModified = value;

                RaisePropertyChanged("IsModified");
            }
        }

        private bool isHighight = false;
        public bool IsHighight
        {
            get
            {
                return isHighight;
            }
            set
            {
                if (isHighight == value)
                {
                    return;
                }

                isHighight = value;

                RaisePropertyChanged("IsHighight");
            }
        }

        private bool isVisible = true;
        public bool IsVisible
        {
            get
            {
                return isVisible;
            }
            set
            {
                if (isVisible == value)
                {
                    return;
                }

                isVisible = value;

                RaisePropertyChanged("IsVisible");
            }
        }

        // 作为tree的节点数据源时, 是否处于编辑状态
        private bool isInEditMode = false;
        public bool IsInEditMode
        {
            get
            {
                return isInEditMode;
            }
            set
            {
                if (isInEditMode == value)
                {
                    return;
                }

                isInEditMode = value;

                RaisePropertyChanged("IsInEditMode");
            }
        }

        private bool isExpanded = true;
        public bool IsExpanded
        {
            get
            {
                return isExpanded;
            }
            set
            {
                if (isExpanded == value)
                {
                    return;
                }

                isExpanded = value;

                RaisePropertyChanged("IsExpanded");
            }
        }

        private bool isSelected = false;
        public bool IsSelected
        {
            get
            {
                return isSelected;
            }
            set
            {
                if (isSelected == value)
                {
                    return;
                }

                isSelected = value;

                RaisePropertyChanged("IsSelected");
            }
        }

        public FileTreeNodeViewModel Parent { get; private set; }

        public ObservableCollection<FileTreeNodeViewModel> Children { get; private set; }

        // 完整路径
        public String FullPath { get; set; }

        // 文件中的Service集合
        private ObservableCollection<ServiceTreeNodeViewModel> serviceCollection;
        public ObservableCollection<ServiceTreeNodeViewModel> ServiceCollection
        {
            get
            {
                return serviceCollection;
            }
            set
            {
                if (serviceCollection == value)
                {
                    return;
                }

                serviceCollection = value;

                RaisePropertyChanged("ServiceCollection");
            }
        }
        #endregion

        #region Commands

        public RelayCommand<FileTreeNodeViewModel> CopyFilePathCommand { get; private set; }
        public RelayCommand<String> OnSearchServiceTxtChangedCommand { get; private set; }
        public RelayCommand<ServiceTreeNodeViewModel> CopyServiceNameCommand { get; private set; }

        public RelayCommand<Object> OnServiceTreeNodeSelectionChangedCommand { get; private set; }

        public RelayCommand<FileTreeNodeViewModel> SaveFileNameCommand { get; private set; }

        // F2, 右键菜单
        public RelayCommand<Object> ModifyServiceNameCommand { get; private set; }
        //Enter
        public RelayCommand<Object> SaveServiceOrActionNameCommand { get; private set; }
        //Cancel
        public RelayCommand<Object> CancelEditServiceNameCommand { get; private set; }

        public RelayCommand<Object> DelServiceOrActionNameCommand { get; private set; }


        public RelayCommand<FileTreeNodeViewModel> AddServiceCommand { get; private set; }

        public RelayCommand<Object> OpenLocationFileCommand { get; private set; }
        #endregion

        #region 枚举数据源
        //public IEnumerable<ValueDescription> QXDMList
        //{ get { return EnumHelper.GetAllValuesAndDescriptions<QXDM>(); } }

        //public IEnumerable<ValueDescription> DJLXList
        //{ get { return EnumHelper.GetAllValuesAndDescriptions<DJLX>(); } }
        #endregion

        public void AddChild(FileTreeNodeViewModel child)
        {
            // TODO 先保存
            this.Children.Add(child);
        }

        //public void RemoveChild(TreeNodeViewModel child)
        //{
        //    // TODO 先保存
        //    this.children.Add(child);
        //}

        //递归获取文件路径, 防止文件夹改名 --- 备用
        //private String fullPath(FileTreeNodeViewModel current, String location)
        //{
        //    if (current.Parent == null)
        //    {
        //        return Path.Combine(current.FullPath, location);
        //    }

        //    return Path.Combine(current.Parent.Text, current.Text);
        //}
    }
}
